package java8;

import org.junit.Test;

import java.time.*;
import java.time.format.DateTimeFormatter;
import java.time.temporal.ChronoUnit;
import java.time.temporal.TemporalAdjuster;
import java.time.temporal.TemporalAdjusters;
import java.util.Set;
import java.util.concurrent.TimeUnit;

/**
 * @author lzy
 * @version v1.0
 * Create DateTime: 2018/7/21 10:22
 */
public class TestLocalDateTime {
    // 1. LocalDate LocalTime LocalDateTime
    @Test
    public void test1() {
        LocalDateTime ldt = LocalDateTime.now();
        System.out.println(ldt);

        LocalDateTime ldt2 = LocalDateTime.of(2015, 1, 2, 13, 24, 16);
        System.out.println(ldt2);

        LocalDateTime ldt3 = ldt.plusYears(2);
        System.out.println(ldt3);

        LocalDateTime ldt4 = ldt.minusDays(12);
        System.out.println(ldt4);

        System.out.println(ldt.getDayOfWeek());
        System.out.println(ldt.getDayOfYear());
    }

    /**
     * 2. Instant : 时间戳(以Unix元年： 19070年1月1日 0时0分0秒到某个时间的一个毫秒值)
     * 默认获取UTC时区时间
     */
    @Test
    public void test2() {
        Instant inst1 = Instant.now();
        System.out.println(inst1);

        OffsetDateTime odt = inst1.atOffset(ZoneOffset.ofHours(8));
        System.out.println(odt);

        System.out.println("ms:" + inst1.toEpochMilli());

        Instant inst2 = Instant.ofEpochSecond(1);
        System.out.println(inst2);
    }

    /**
     * 3. Duration:计算两个时间之间的间隔
     * Period：计算两个日期之间的间隔
     */
    @Test
    public void test3() throws InterruptedException {
        Instant ins1 = Instant.now();
        TimeUnit.SECONDS.sleep(5);
        Instant ins2 = Instant.now();
        Duration duration = Duration.between(ins1, ins2);
        System.out.println(duration.toMillis());

        long seconds = duration.get(ChronoUnit.SECONDS);
        System.out.println("seconds:" + seconds);

        System.out.println("---------------------");

        LocalTime lt1 = LocalTime.now();
        TimeUnit.SECONDS.sleep(1);
        LocalTime lt2 = lt1.minusMinutes(30);

        System.out.println(Duration.between(lt1, lt2).toMinutes());


    }

    @Test
    public void test4() {
        LocalDate dt1 = LocalDate.now();
        LocalDate dt2 = LocalDate.of(1985, 4, 5);
        Period period = Period.between(dt2, dt1);

        System.out.println(period.getYears() + "年" + period.getMonths() + "月" + period.getDays() + "日");
        System.out.println(period.toTotalMonths());

        long days = period.get(ChronoUnit.DAYS);
        System.out.println("total days between two days is " + days);
    }

    /**
     * TemporalAdjust : 时间校正器
     */
    @Test
    public void test5() {
        LocalDateTime ldt = LocalDateTime.now();
        System.out.println(ldt);

        LocalDateTime ldt2 = ldt.withDayOfMonth(10);
        System.out.println(ldt2);

        LocalDateTime ldt3 = ldt.with(TemporalAdjusters.next(DayOfWeek.FRIDAY));
        System.out.println(ldt3);

        // 定义下一工作日
        TemporalAdjuster adjuster = l -> {
            LocalDateTime ldt4 = (LocalDateTime) l;
            DayOfWeek dow = ldt4.getDayOfWeek();
            if (dow.equals(DayOfWeek.FRIDAY)) {
                return ldt4.plusDays(3);
            } else if (dow.equals(DayOfWeek.SATURDAY)) {
                return ldt4.plusDays(2);
            } else {
                return ldt4.plusDays(1);
            }
        };

        LocalDateTime ldt5 = ldt.with(adjuster);

        System.out.println(ldt5);
    }

    /**
     * DateTimeFormatter: 格式化时间/日期
     */
    @Test
    public void test6() {
        DateTimeFormatter formatter = DateTimeFormatter.ISO_DATE;
        LocalDateTime ldt = LocalDateTime.now();

        String strDate = ldt.format(formatter);
        System.out.println(strDate);
        strDate = ldt.format(DateTimeFormatter.ISO_TIME);
        System.out.println(strDate);

        System.out.println("----------------------------");

        DateTimeFormatter dtf = DateTimeFormatter.ofPattern("yyyy年MM月dd日 HH:mm:ss");
        String dt2 = dtf.format(ldt);
        System.out.println(dt2);

        LocalDateTime newDate = LocalDateTime.parse(dt2, dtf);
        System.out.println(newDate);
    }

    /**
     * ZoneDate\ZoneTime\ZoneDateTime
     */
    @Test
    public void test7(){
        Set<String> set = ZoneId.getAvailableZoneIds();
        set.forEach(System.out::println);
    }
    
    @Test
    public void test8(){
        LocalDateTime ldt = LocalDateTime.now(ZoneId.of("US/Pacific"));
        System.out.println(ldt);

        LocalDateTime ldt2 = LocalDateTime.now();
        ZonedDateTime zdt = ldt2.atZone(ZoneId.of("US/Pacific"));
        System.out.println(zdt);
    }
}
